home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1996 February: Tool Chest / Apple Developer CD Series Tool Chest February 1996 (Apple Computer)(1996).iso / Sample Code / System 7.0 Samples / Edition Manager / Windows.c < prev   
Encoding:
C/C++ Source or Header  |  1994-11-18  |  15.9 KB  |  426 lines  |  [TEXT/MPS ]

  1. /*------------------------------------------------------------------------------
  2.  *
  3.  *  Apple Developer Technical Support
  4.  *
  5.  *  Text section handling routines
  6.  *
  7.  *  Program:    EditionSample
  8.  *  File:       Windows.c -    C Source
  9.  *
  10.  *  by:         C.K. Haun <TR>
  11.  *
  12.  *  Copyright © 1990,1991 Apple Computer, Inc.
  13.  *  All rights reserved.
  14.  *
  15.  *------------------------------------------------------------------------------
  16.  * This file contains some of our window handling routines.  I created it 
  17.  * primarily to take some of the clutter out of the main.c file.
  18.  * It also contains the clipboard handlers
  19.  *----------------------------------------------------------------------------*/
  20.  
  21. #define __MYWINDOWS__
  22.  
  23. #pragma segment MyWindows
  24. #pragma load "EdSampheaders"                                /* see the Buildheaders.c file */
  25.  
  26. #include "EdSampdefines.h"
  27. /* protos for this file */
  28. void ChangePlane(WindowPtr twindow);
  29. Boolean IsAppWindow(WindowPtr window);
  30. Boolean IsDAWindow(WindowPtr window);
  31. WindowPtr AddNewWindow(Boolean showIt);
  32. void CloseMyWindow(WindowPtr theClose);
  33.  
  34. /* clipboard stuff */
  35. void DrawClip(WindowPtr windowIn);
  36. void ClipClick(WindowPtr twindow);
  37. void CloseClip(void);
  38. void UpdateScrap(void);
  39. void SpitClip(void);
  40.  
  41.  
  42.  
  43. /* external references */
  44. extern MenuHandle gAppleMenuHandle, gFileMenuHandle, gEditMenuHandle, gToolMenuHandle, gAdditionalMenu;
  45. extern WindowPtr gCurrentWindow;                            /* window currently frontmost */
  46. extern WindowPtr gClipWindowPtr;                            /* our clipboard window */
  47. extern WindowPtr gActionWindows;                            /* start of our window list */
  48. extern short gWindowCount;                                  /* current number of windows, since I'm restricting to 10 */
  49. extern Boolean gStop;                                       /* Stop flag for this app */
  50. extern unsigned long gMasterWindowID;                       /* for section tracking */
  51. extern Rect gShowPubRect;                                   /* rectangle of the currently selected publisher */
  52. extern Rect gShowSubRect;                                   /* rectangle of the currently selected subscriber */
  53. extern SectionHandle gShowingSecHandle;                     /* currently selected section */
  54. extern SectionHandle gClipSection;                          /* if the clipboard contains a section */
  55. extern PicHandle gClipPict;                                 /* for the section picture */
  56. extern Boolean gShowPub;                                    /* telling if a publisher or subscriber */
  57. extern Boolean gShowSub;                                    /* border should be displayed */
  58. extern Boolean gShowingAll;                                 /* show all borders toggle */
  59. extern Boolean gInBackground;                               /* Where Are We? */
  60. extern Boolean gExpanded;                                   /* flag for expanded dialogs, for this sample */
  61. extern Boolean gResizeSub;                                  /* resize flag for this sample */
  62. extern short gClipHasContents;                              /* indicates the contents of the clipboard (PICT, TEXT, section ) */
  63. extern short actsToIDs[];
  64. extern void DrawFull(windowCHandle theWind, WindowPtr theWindPtr);
  65. extern void SaveMe(windowCHandle theWind, WindowPtr theWindPtr);
  66. extern void DoDocumentClick(WindowPtr twindow);
  67. extern Handle gScrapData;  
  68.  
  69.  
  70.  
  71.  
  72.  
  73.  
  74. /* AddNewWindow creates and initializes a new document window. */
  75. /* It returns false in this example if there are already 10 windows open. */
  76. WindowPtr AddNewWindow(Boolean showIt)
  77. {
  78.     windowCHandle setControls;
  79.     WindowPtr tempWP;
  80.     Handle tempHand;
  81.     short cnt = 0;
  82.     Str31 wtitle;
  83.     if (gWindowCount > 9)
  84.         return(false);
  85.     tempWP = GetNewWindow(kDocWindow, 0, (WindowPtr)-1);        /* get a new window */
  86.     /* and add it to our list by finding the current last window in the chain  */
  87.     if (gActionWindows == nil) {                            /* there are no windows yet */
  88.         gActionWindows = tempWP;
  89.     } else {
  90.         Boolean fred = true;
  91.         setControls = (windowCHandle)GetWRefCon(gActionWindows);
  92.         do {
  93.             if ((*setControls)->nextWindow == nil)
  94.                 fred = false;
  95.             else
  96.                 setControls = (windowCHandle)((WindowPeek)(*setControls)->nextWindow)->refCon;
  97.         } while (fred);
  98.         (*setControls)->nextWindow = tempWP;
  99.     }
  100.     gCurrentWindow = tempWP;                                /* make it the current window */
  101.     tempHand = NewHandle(sizeof(windowControl));            /* add our control structure to it */
  102.     ((WindowPeek)tempWP)->refCon = tempHand;
  103.     setControls = (windowCHandle)((WindowPeek)tempWP)->refCon;      /* and put it where we can use it */
  104.     HLock((Handle)setControls);                             /* lock it down */
  105.     /* add pointers to our procedures for drawing, saving, and closing */
  106.     (*setControls)->drawMe = (ProcPtr)DrawFull;
  107.     (*setControls)->saveMe = (ProcPtr)SaveMe;
  108.     (*setControls)->closeMe = (ProcPtr)CloseMyWindow;
  109.     (*setControls)->clickMe = (ProcPtr)DoDocumentClick;
  110.     /* now initialize all our required handles, and move 'em hi */
  111.     (*setControls)->lineList = (myLineHandle)NewHandle(0);
  112.     (*setControls)->rectList = NewHandle(0);
  113.     (*setControls)->ovalList = NewHandle(0);
  114.     (*setControls)->pubs = NewHandle(0);
  115.     (*setControls)->pubRects = NewHandle(0);
  116.     (*setControls)->numPubs = 0;
  117.     (*setControls)->subs = NewHandle(0);
  118.     (*setControls)->subRects = NewHandle(0);
  119.     (*setControls)->subDataHandle = NewHandle(0);
  120.     (*setControls)->numSubs = 0;
  121.     (*setControls)->pictHandle = NewHandle(0);
  122.     (*setControls)->pictRects = NewHandle(0);
  123.     (*setControls)->numPicts = 0;
  124.     (*setControls)->nextWindow = nil;
  125.     /* initialize our control codes and counts */
  126.     (*setControls)->lineCount = 0;
  127.     (*setControls)->rectCount = 0;
  128.     (*setControls)->ovalCount = 0;
  129.     (*setControls)->currentAction = 0;
  130.     (*setControls)->undoAction = 0;
  131.     (*setControls)->hasSelection = false;
  132.     (*setControls)->windowDirty = false;
  133.     (*setControls)->windowID = gMasterWindowID;
  134.     gMasterWindowID += 10000;                               /* update for next window */
  135.     /* clear the file spec for the file this document will be saved to */
  136.     (*setControls)->fileAliasHandle = (AliasHandle)NewHandle(0);
  137.     (*setControls)->boxHandle = nil;
  138.     (*setControls)->textSections = nil;
  139.     /* if there already is a window (or more) add a count to this title */
  140.     if (showIt) {
  141.         GetWTitle(tempWP, wtitle);
  142.         if (gWindowCount) {
  143.             wtitle[9] = gWindowCount | 0x30;                /* make number ascii */
  144.             
  145.         } else {                                            /* take off the trailing space */
  146.             wtitle[0]--;
  147.         }
  148.         SetWTitle(tempWP, wtitle);
  149.         ShowWindow(tempWP);                                 /* show it */
  150.     }
  151.     HUnlock((Handle)setControls);
  152.     SetPort(tempWP);
  153.     gWindowCount++;
  154.     SetUndo(0, false);                                      /* since it is the current window, set all the actions to default */
  155.     SetCurAction(0);
  156.     SetMyCursor(0);
  157.     SwitchChecks(0);
  158.     SetWMenus(true);
  159.     if (gWindowCount > 9) {
  160.         DisableItem(gFileMenuHandle, kOpenItem);
  161.         DisableItem(gFileMenuHandle, kNewItem);
  162.     }
  163.     return(tempWP);
  164. }
  165.  
  166. /* end AddNewWindow */
  167.  
  168. /* CloseMyWindow closes the window and disposes of all the memory 
  169. *   associated with it.  It also calls HandleSections (sic) to UnRegister
  170. * all the editions associated with this window 
  171. */
  172.  
  173. void CloseMyWindow(WindowPtr theClose)
  174. {
  175.     windowCHandle theWind;
  176.     windowCHandle tempWC;
  177.     WindowPtr tempWP;
  178.     short alBack;
  179.     register qq;
  180.     PicHandle *tempPicHandPtr;
  181.     theWind = (windowCHandle)GetWRefCon(theClose);
  182.     HLock((Handle)theWind);
  183.     if ((*theWind)->windowDirty) {
  184.         Str255 windName;
  185.         GetWTitle(theClose, windName);
  186.         ParamText(windName, "", "", "");
  187.         alBack = Alert(kDirtyAlert, nil);
  188.         if (alBack == kOK)
  189.             (ProcPtr)(*(theWind))->saveMe(theWind, theClose);
  190.         if (alBack == kCancel) {
  191.             gStop = false;
  192.             return;
  193.         }
  194.     }
  195.     DisposeHandle((*theWind)->rectList);
  196.     DisposeHandle((*theWind)->ovalList);
  197.     DisposeHandle((Handle)(*theWind)->lineList);
  198.     HandleSectionSave(theWind, false, true, nil);
  199.     DisposeHandle((*theWind)->pubs);
  200.     DisposeHandle((*theWind)->pubRects);
  201.     DisposeHandle((*theWind)->subs);
  202.     DisposeHandle((*theWind)->subRects);
  203.     DisposeHandle((Handle)(*theWind)->fileAliasHandle);
  204.     if ((*theWind)->boxHandle != nil)
  205.         TEDispose((*theWind)->boxHandle);
  206.     /* if there are any pictures, kill them too */
  207.     if ((*theWind)->numPicts) {
  208.         HLock((*theWind)->pictHandle);
  209.         tempPicHandPtr = (PicHandle *)*(*theWind)->pictHandle;
  210.         for (qq = 0; qq < (*theWind)->numPicts; qq++) {     /* rectangles are handled in the HandleSectionSave */
  211.             KillPicture(*tempPicHandPtr);
  212.             tempPicHandPtr += 1;
  213.         }
  214.     }
  215.     DisposeHandle((*theWind)->pictHandle);
  216.     DisposeHandle((*theWind)->pictRects);
  217.     
  218.     /* find this window in the list, remove it and remake the link */
  219.     if (gActionWindows != theClose) {
  220.         Boolean fred = true;
  221.         tempWP = gActionWindows;
  222.         do {
  223.             tempWC = (windowCHandle)GetWRefCon(tempWP);
  224.             if ((*tempWC)->nextWindow == theClose)
  225.                 fred = false;
  226.             else
  227.                 tempWP = (*tempWC)->nextWindow;
  228.         } while (fred);
  229.         (*tempWC)->nextWindow = (*theWind)->nextWindow;
  230.     } else {
  231.         /* first in the list, just kill this one */
  232.         gActionWindows = (*theWind)->nextWindow;            /* may be nil, that's fine */
  233.         tempWP = gActionWindows;
  234.     }
  235.     /* and get rid of this one */
  236.     DisposeHandle((Handle)theWind);
  237.     CloseWindow(theClose);
  238.     gWindowCount--;
  239.     gCurrentWindow = tempWP;
  240.     if (tempWP != nil) {
  241.         SelectWindow(tempWP);
  242.         SetPort(tempWP);
  243.         gShowingSecHandle = nil;
  244.         gShowPub = false;
  245.         gShowSub = false;
  246.     } else {
  247.         gCurrentWindow = nil;
  248.         SetWMenus(false);
  249.         gShowingSecHandle = nil;
  250.         gShowPub = false;
  251.         gShowSub = false;
  252.     }
  253.     EnableItem(gFileMenuHandle, kOpenItem);
  254.     EnableItem(gFileMenuHandle, kNewItem);
  255.     
  256. }
  257.  
  258.  
  259.  
  260.  
  261. /* ChangePlane does the housekeeping we need to do when a window comes to */
  262. /* the front, swapping menu checks, setting the cursor, and so on */
  263. void ChangePlane(WindowPtr twindow)
  264. {
  265.     short temp;
  266.     windowCHandle shortname;
  267.     /* Before the swap kill any current borders */
  268.     DeBorderSelection();
  269.     SelectWindow(twindow);                                  /* select the window */
  270.     /* deactivate the textedit record of the old window, if there is one */
  271.     if (gCurrentWindow != nil) {
  272.         windowCHandle tempCH = (windowCHandle)GetWRefCon(gCurrentWindow);
  273.         if ((*tempCH)->boxHandle != nil)
  274.             TEDeactivate((*tempCH)->boxHandle);
  275.     }
  276.     if (gCurrentWindow == gClipWindowPtr) {
  277.         SetWMenus(true);
  278.         /* turn tool menus back on if last window was clipbaord */
  279.     }
  280.     gCurrentWindow = twindow;                               /* make it our current window */
  281.     SetUndo(0, true);                                       /* tell SetUndo to pull the undo item value out of the current record */
  282.     shortname = (windowCHandle)GetWRefCon(gCurrentWindow);
  283.     HLock((Handle)shortname);
  284.     temp = (*shortname)->currentAction;                     /* pull the last action the */
  285.     HUnlock((Handle)shortname);                             /* user was performing out of the */
  286.     SetCurAction(temp);                                     /* window record */
  287.     SetMyCursor(actsToIDs[temp]);                           /* set the right cursor */
  288.     SwitchChecks(actsToIDs[temp]);                          /* check the right menu item */
  289.     gShowPub = gShowSub = false;                            /* selections go away when windows */
  290.     gShowingSecHandle = nil;
  291.     if ((*shortname)->boxHandle != nil)
  292.         TEActivate((*shortname)->boxHandle);
  293.     if (twindow == gClipWindowPtr) {
  294.         SetWMenus(false);
  295.     }
  296.     /* change plane */
  297. }
  298.  
  299. /* end ChangePlane */
  300.  
  301. Boolean IsAppWindow(WindowPtr window)
  302. {
  303.     short windowKind;
  304.     if (window == nil)
  305.         return false;
  306.     else {                                                  /* application windows have windowKinds = userKind (8) */
  307.         windowKind = ((WindowPeek)window)->windowKind;
  308.         return(windowKind = userKind);
  309.     }
  310. }
  311.  
  312. /* end IsAppWindow*/
  313.  
  314. /* Check to see if a window belongs to a desk accessory. */
  315.  
  316. Boolean IsDAWindow(WindowPtr window)
  317. {
  318.     if (window == nil)
  319.         return false;
  320.     else                                                    /* DA windows have negative windowKinds */
  321.         return((WindowPeek)window)->windowKind < 0;
  322. }
  323.  
  324. /* end IsDAWindow*/
  325.  
  326. void DrawClip(WindowPtr windowIn)
  327. {
  328.     Str63 clipString;
  329.     MoveTo(10, 10);
  330.     GetIndString(clipString, kClipBoardStrings, 1);
  331.     DrawString(clipString);
  332.     GetIndString(clipString, kClipBoardStrings, gClipHasContents);
  333.     DrawString(clipString);
  334.     MoveTo(0, 13);
  335.     LineTo(gClipWindowPtr->portRect.right, 13);
  336.     HLock(gScrapData);
  337.     if ((GetHandleSize(gScrapData) != 0) && gScrapData) {
  338.         Rect picRect;
  339.         picRect = ((*(PicHandle)gScrapData))->picFrame;
  340.         OffsetRect(&picRect, 0, 15);
  341.         DrawPicture((PicHandle)gScrapData, &picRect);
  342.     }
  343.     HUnlock(gScrapData);
  344.     
  345. }
  346.  
  347. /* end DrawClip */
  348.  
  349. void ClipClick(WindowPtr twindow)
  350. {     /* nothing happens on a clipboard click, it's in here for whenever I put scroll bars in */
  351. }
  352. void CloseClip(void)
  353. {
  354.     ChangePlane(gClipWindowPtr);
  355.     HideWindow(gClipWindowPtr);
  356.     if (FrontWindow() != nil)
  357.         ChangePlane(FrontWindow());
  358.     SetMenuItemText(gEditMenuHandle, kClapNum, "\pShow Clipboard");
  359. }
  360.  
  361. void UpdateScrap(void)
  362. {
  363.     
  364.     Handle textData;
  365.     long myOffset;
  366.     long length;
  367.     textData = NewHandle(0);
  368.     if (gClipHasContents == kClipHasSub) {
  369.     } else {
  370.         /* show standard scrap types, prefering pictures */
  371.         length = GetScrap(gScrapData, 'PICT', &myOffset);
  372.         if (length < 0) {
  373.             if (length == noTypeErr) {
  374.                 length = GetScrap(textData, 'TEXT', &myOffset);
  375.                 /* if it's text, I'm going to make it into a picture for my clipboard display, makes things */
  376.                 /* easier in my draw proc */
  377.                 if (length > 0) {
  378.                     DisposeHandle(gScrapData);               /* kill the old one */
  379.                     gScrapData = (Handle)OpenPicture(&gClipWindowPtr->portRect);
  380.                     HLock(textData);
  381.                     TETextBox(*textData, length, &gClipWindowPtr->portRect, teJustLeft);
  382.                     HUnlock(textData);
  383.                     ClosePicture();
  384.                     gClipHasContents = kClipHasText;
  385.                 }
  386.             } else {                                        /* another type of error, like nothing available at all */
  387.                 MySetHandleSize(gScrapData, 0);
  388.                 gClipHasContents = kClipEmpty;
  389.             }
  390.         } else {
  391.             /* set the pict rect so it's in the upper left of our clipboard */
  392.             gClipHasContents = kClipHasPict;
  393.             OffsetRect(&((*(PicHandle)gScrapData))->picFrame, (((*(PicHandle)gScrapData))->picFrame.left * -1),
  394.                        (((*(PicHandle)gScrapData))->picFrame.top * -1) + 11);
  395.         }
  396.     }
  397.     DisposeHandle(textData);
  398.     if (((WindowPeek)gClipWindowPtr)->visible) {
  399.         WindowPtr temp;
  400.         GetPort(&temp);
  401.         SetPort(gClipWindowPtr);
  402.         InvalRect(&gClipWindowPtr->portRect);
  403.         SetPort(temp);
  404.     }
  405. }
  406.  
  407. /* end updatescrap */
  408.  
  409. /* SpitClip spits our private subscription out to the general clipboard as a PICT type scrap */
  410. /* when we go in the background.  Does nothing if it's not a subscription, since it'll already */
  411. /* be right. */
  412.  
  413.  
  414. void SpitClip(void)
  415. {
  416.     if (gClipHasContents == kClipHasSub) {
  417.         ZeroScrap();
  418.         HLock(gScrapData);
  419.         PutScrap(GetHandleSize(gScrapData), 'PICT', *gScrapData);
  420.     
  421.     }
  422. }
  423.  
  424.  
  425. #undef __MYWINDOWS__
  426.